package cn.masterj.springcloud.service.fallback;

import com.alibaba.csp.sentinel.slots.block.BlockException;

/**
 * @author masterJ
 * @create 2020-04-18 16:08
 */
public class BlockFallbackFactory {

    /**
     * 属于不满足sentinel上配置的各种规则的异常（异常都是BlockException的子类）时就进入fallback = "fallbackHandler"
     * @SentinelResource(value = "testE", blockHandler = "blockHandler" , blockHandlerClass = BlockFallbackFactory.class,fallback = "fallbackHandler", fallbackClass = BlockFallbackFactory.class)
     * blockHandler 函数访问范围需要是 public
     * 返回类型需要与原方法相匹配
     * 参数类型需要和原方法相匹配并且最后加一个额外的参数，类型为 BlockException **********************************************
     * blockHandler 函数默认需要和原方法在同一个类中
     * @param suibian   类型要想匹配，参数名随意
     * @param e         异常类型必须是BlockException，否则属于sentinel上配置的流控，降级，热点等规则异常时也会进入下面的fallback，而不是blockHandler
     * @return
     */
    public static String blockHandler(Long suibian, BlockException e){
        System.out.println("-----------------------blockHandler--------" );
        e.printStackTrace();
        return "blockHandler" + e.getRule();
    }

    /**
     * 属于方法异常的就进入fallback = "fallbackHandler"
     * @SentinelResource(value = "testE", blockHandler = "blockHandler" , blockHandlerClass = BlockFallbackFactory.class,fallback = "fallbackHandler", fallbackClass = BlockFallbackFactory.class)
     * fallbackHandler 函数访问范围需要是 public
     * 返回类型需要与原方法相匹配
     * 参数类型需要和原方法相匹配并且最后加一个额外的参数，类型为 Throwable **********************************************
     * fallbackHandler 函数默认需要和原方法在同一个类中
     * @param suibian   类型要想匹配，参数名随意
     * @param e         异常类型写异常的顶级类就行
     * @return
     */
    public static String fallbackHandler(Long suibian,Throwable e){
        System.out.println("-----------------------fallbackHandler------" );
        e.printStackTrace();
        return "fallbackHandler" + e.getMessage();
    }

    // 思考，那怎么实现真正的统一呢，即实现  不同参数类型，或参数个数的方式怎么使用同一个blockHandler，和fallback


}
